package cate.game.activity.serverprogress;

import cate.common.table.activity.serverprogress.base.ServerProgressBaseRow;
import cate.common.table.activity.serverprogress.reward.ServerProgressRewardRow;
import cate.common.table.d.GDFunc;
import cate.common.table.d.GDObj;
import cate.common.table.d.GDOperation;
import cate.common.util.GameResult;
import cate.game.activity.base.core.RoleActivitySingle;
import cate.game.activity.merge.msg.MergeServerProgressInfoResp;
import cate.game.res.MixRes;
import cate.game.res.MixResAdder;
import cate.game.role.Role;
import com.fasterxml.jackson.annotation.JsonIgnore;
import easy.java.dev.note.NoteClass;
import easy.java.dev.note.NoteField;

import java.util.HashMap;
import java.util.Map;

@NoteClass("全服进度活动")
public class ServerProgressActivity extends RoleActivitySingle {
    @NoteField("奖励领取状态")
    public Map<Integer, Boolean> rewardsGot;

    @Override
    public void initialize(Role role) {
        super.initialize(role);
        if (rewardsGot == null) {
            rewardsGot = new HashMap<>();
        }
        role.getActivity().registerRecharge(this, this::onPay);
    }

    @Override
    public void onRoleOpen() {

    }

    @Override
    public void onRoleEnd() {
        rewardsGot.clear();
    }

    @Override
    public void initSend() {
        ServerProgressActivityHandler handler = role.getGame().activityGlobal.getEnableHandler(funcId());
        if (handler != null) {
            long globalProgress = handler.getGlobalProgress();
            switch (funcId()) {
                case GDFunc.MergeAct.MERGE_ACT_SERVER_TARGET:
                    role.sendNow(new MergeServerProgressInfoResp(globalProgress, this));
                    break;
                default:
                    break;
            }
        }
    }

    @Override
    public void excelCheck() {
        Map<Integer, ServerProgressRewardRow> allRewardConfigs = getAllRewardConfigs();
        if (allRewardConfigs.isEmpty()) {
            rewardsGot.clear();
        } else {
            rewardsGot.entrySet().removeIf(entry -> !allRewardConfigs.containsKey(entry.getKey()));
            allRewardConfigs.entrySet().stream().filter(entry -> !rewardsGot.containsKey(entry.getKey()))
                    .forEach(entry -> rewardsGot.put(entry.getKey(), false));
        }
    }

    /**
     * 获取操作编号
     */
    @JsonIgnore
    private int getGDOperation() {
        switch (funcId()) {
            case GDFunc.MergeAct.MERGE_ACT_SERVER_TARGET:
                return GDOperation.MERGE_SERVER_TARGET;
            default:
                break;
        }
        return GDOperation.NULL;
    }

    /**
     * 获取基础配置
     */
    @JsonIgnore
    private ServerProgressBaseRow getBaseConfig() {
        switch (funcId()) {
            case GDFunc.MergeAct.MERGE_ACT_SERVER_TARGET:
                return role.getGame().table.mergeSP.base.get(configTid());
            default:
                break;
        }
        return null;
    }

    /**
     * 获取所有奖励配置
     */
    @JsonIgnore
    private Map<Integer, ServerProgressRewardRow> getAllRewardConfigs() {
        Map<Integer, ServerProgressRewardRow> retMap = new HashMap<>();
        switch (funcId()) {
            case GDFunc.MergeAct.MERGE_ACT_SERVER_TARGET:
                role.getGame().table.mergeSP.reward.getList().stream()
                        .filter(row -> row.configTid == configTid())
                        .forEach(row -> retMap.put(row.id, row));
                break;
            default:
                break;
        }
        return retMap;
    }

    /**
     * 获取奖励配置
     *
     * @param tid 配置ID
     */
    @JsonIgnore
    private ServerProgressRewardRow getRewardConfig(int tid) {
        switch (funcId()) {
            case GDFunc.MergeAct.MERGE_ACT_SERVER_TARGET:
                return role.getGame().table.mergeSP.reward.get(tid);
            default:
                break;
        }
        return null;
    }

    /**
     * 领取任务奖励处理
     *
     * @param reward 显示奖励
     * @return 领取结果 携带真实奖励
     */
    public GameResult<MixRes> onGetTaskReward(MixRes reward) {
        GameResult<MixRes> r = new GameResult<>();
        ServerProgressBaseRow config = getBaseConfig();
        if (config == null) {
            return r.fail("配置不存在");
        }
        ServerProgressActivityHandler handler = role.getGame().activityGlobal.getEnableHandler(funcId());
        if (handler == null) {
            return r.fail("活动未开启");
        }
        int itemTid = config.pointTid;
        int progressNum = (int) reward.count(GDObj.Type.NUM, itemTid);
        if (progressNum > 0) {
            handler.addGlobalProgress(progressNum);
        }
        MixRes realRes = reward.copy();
        realRes.items.removeIf(item -> item.type == GDObj.Type.NUM && item.tid == itemTid);
        return r.success("success", realRes);
    }

    /**
     * 领取进度奖励
     *
     * @param tid 配置ID
     * @return 领取结果 携带活动类
     */
    public GameResult<Void> onGetProgressReward(int tid) {
        GameResult<Void> r = new GameResult<>();
        if (!rewardsGot.containsKey(tid)) {
            return r.fail("找不到配置");
        }
        if (rewardsGot.get(tid)) {
            return r.fail("奖励已领取");
        }
        ServerProgressRewardRow rewardConfig = getRewardConfig(tid);
        if (rewardConfig == null) {
            return r.fail("配置找不到");
        }
        ServerProgressActivityHandler handler = role.getGame().activityGlobal.getEnableHandler(funcId());
        if (handler == null) {
            return r.fail("活动未开启");
        }
        if (handler.getGlobalProgress() < rewardConfig.needProgress) {
            return r.fail("进度不足");
        }
        MixRes reward = new MixRes(rewardConfig.rewardStr);
        if (reward.isEmpty()) {
            return r.fail("奖励配置错误");
        }
        rewardsGot.put(tid, true);
        new MixResAdder().setRes(reward)
                .setDialogReward(true)
                .setSendMailWhenFull(true)
                .setOperation(getGDOperation())
                .setOperationSub(tid)
                .exe(role);
        return r.success();
    }

    public void onPay(long payCents) {
        ServerProgressActivityHandler activityHandler = role.getGame().activityGlobal.getEnableHandler(funcId());
        if (activityHandler != null) {
            activityHandler.addGlobalProgress(payCents / 100);
        }
    }
}
